/******
    ************************************************************************
    ******
    ** @project : XDrive_Step
    ** @brief   : Stepper motor with multi-function interface and closed loop function. 
    ** @brief   : 具有多功能接口和闭环功能的步进电机
    ** @author  : unlir (知不知啊)
    ** @contacts: QQ.1354077136
    ******
    ** @address : https://github.com/unlir/XDrive
    ******
    ************************************************************************
    ******
    ** {Stepper motor with multi-function interface and closed loop function.}
    ** Copyright (c) {2020}  {unlir(知不知啊)}
    ** 
    ** This program is free software: you can redistribute it and/or modify
    ** it under the terms of the GNU General Public License as published by
    ** the Free Software Foundation, either version 3 of the License, or
    ** (at your option) any later version.
    ** 
    ** This program is distributed in the hope that it will be useful,
    ** but WITHOUT ANY WARRANTY; without even the implied warranty of
    ** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
    ** GNU General Public License for more details.
    ** 
    ** You should have received a copy of the GNU General Public License
    ** along with this program.  If not, see <http://www.gnu.org/licenses/>.
    ******
    ************************************************************************
******/

//Oneself
#include "tim.h"


/********** HwElec **********/
/********** HwElec **********/
/********** HwElec **********/
/**
  * @brief  TIM_PWMtoDAC初始化
  * @param  NULL
  * @retval NULL
**/
void REIN_TIM_HwElec_Init(void)
{
}

/********** SIGNAL **********/
/********** SIGNAL **********/
/********** SIGNAL **********/
/**
  * @brief  TIM_SIGNAL_PUL初始化
  * @param  NULL
  * @retval NULL
**/
void REIN_TIM_SIGNAL_COUNT_Init(void)
{
    /* GPIO初始化 */
  /* GPIO Ports Clock Enable*/
    SIGNAL_COUNT_PUL_CLK_ENABLE();            //启用SIGNAL_COUNT_PUL端口时钟
    SIGNAL_COUNT_TIM_CLK_ENABLE();        //启用TIM时钟
  /*Configure GPIO pin*/
    gpio_init(SIGNAL_COUNT_PUL_GPIO_Port, GPIO_MODE_IN_FLOATING, GPIO_OSPEED_50MHZ, SIGNAL_COUNT_PUL_Pin);

    /* TIM初始化 */
    timer_parameter_struct timer_init_struct;
  
    timer_struct_para_init(&timer_init_struct);
    timer_init_struct.prescaler         = 0;          // 预分频:0
    timer_init_struct.alignedmode       = TIMER_COUNTER_EDGE;
    timer_init_struct.counterdirection  = TIMER_COUNTER_UP;  // 向上计数
    timer_init_struct.period            = 65535;      // 16位周期
    timer_init_struct.clockdivision     = TIMER_CKDIV_DIV1; // 不分频
    timer_init_struct.repetitioncounter = 0;
    timer_init(SIGNAL_COUNT_Get_TIM, &timer_init_struct);

    // sSlaveConfig.TriggerPolarity = TIM_TRIGGERPOLARITY_RISING;    //上升沿触发
    // sSlaveConfig.TriggerFilter = 4;                                                            //滤波参数(FDIV2_N6)

    // 从模式配置（外部时钟模式1）
    timer_slave_mode_select(SIGNAL_COUNT_Get_TIM, TIMER_SLAVE_MODE_EXTERNAL0);
    timer_input_trigger_source_select(SIGNAL_COUNT_Get_TIM, TIMER_SMCFG_TRGSEL_CI0FE0); // 类似TI1FP1
                //上升沿触发
                //滤波参数(FDIV2_N6)

    // 主模式配置
    timer_master_output_trigger_source_select(SIGNAL_COUNT_Get_TIM, TIMER_TRI_OUT_SRC_RESET); // 主机模式触发复位
    timer_master_slave_mode_config(SIGNAL_COUNT_Get_TIM, TIMER_MASTER_SLAVE_MODE_DISABLE); // 禁用主机模式

    /*begin work*/
    timer_enable(SIGNAL_COUNT_Get_HTIM);
}

/**
  * @brief  TIM_SIGNAL_COUNT清理
  * @param  NULL
  * @retval NULL
**/
void REIN_TIM_SIGNAL_COUNT_DeInit(void)
{
    timer_disable(SIGNAL_COUNT_Get_HTIM);                                        //停止TIM
    gpio_init(SIGNAL_COUNT_PUL_GPIO_Port,  GPIO_MODE_AIN, GPIO_OSPEED_50MHZ, SIGNAL_COUNT_PUL_Pin);
}    

/**
  * @brief  TIM_SIGNAL_PWM初始化
  * @param  NULL
  * @retval NULL
**/
void REIN_TIM_SIGNAL_PWM_Init(void)
{
    /* 定时器初始化 */
    timer_parameter_struct timer_init_struct;
    timer_ic_parameter_struct ic_init_struct;

    /* GPIO初始化 */
    /* GPIO Ports Clock Enable*/
    SIGNAL_PWM_PUL_CLK_ENABLE();        //启用SIGNAL_PWM_PUL端口时钟
    SIGNAL_PWM_TIM_CLK_ENABLE();        //启用TIM时钟
    /*Configure GPIO pin*/
    gpio_init(SIGNAL_PWM_PUL_GPIO_Port, GPIO_MODE_IN_FLOATING, GPIO_OSPEED_50MHZ, SIGNAL_PWM_PUL_Pin);

    /* 定时器基本配置 */
    timer_struct_para_init(&timer_init_struct);
    timer_init_struct.prescaler         = 71;          // 72MHz/(71+1)=1MHz
    timer_init_struct.alignedmode       = TIMER_COUNTER_EDGE;
    timer_init_struct.counterdirection  = TIMER_COUNTER_UP;
    timer_init_struct.period            = 65535;       // 65.536ms周期
    timer_init_struct.clockdivision     = TIMER_CKDIV_DIV1;
    timer_init_struct.repetitioncounter = 0;
    timer_init(SIGNAL_PWM_Get_HTIM, &timer_init_struct);
    
    /* 从模式配置（复位模式）*/
    timer_slave_mode_select(SIGNAL_PWM_Get_HTIM, TIMER_SLAVE_MODE_RESTART);
    timer_input_trigger_source_select(SIGNAL_PWM_Get_HTIM, TIMER_SMCFG_TRGSEL_CI0FE0);

    //主模式配置
    timer_master_output_trigger_source_select(SIGNAL_PWM_Get_HTIM, TIMER_TRI_OUT_SRC_RESET); // 主模式：复位
    timer_master_slave_mode_config(SIGNAL_PWM_Get_HTIM, TIMER_MASTER_SLAVE_MODE_DISABLE);       // 禁用主机模式

    ic_init_struct.icpolarity  = TIMER_IC_POLARITY_RISING;
    ic_init_struct.icselection = TIMER_IC_SELECTION_DIRECTTI;
    ic_init_struct.icprescaler = TIMER_IC_PSC_DIV1;
    ic_init_struct.icfilter    = 0;
    timer_input_capture_config(SIGNAL_PWM_Get_HTIM, TIMER_CH_0, &ic_init_struct);

    // 通道2配置（下降沿，间接输入）
    ic_init_struct.icpolarity  = TIMER_IC_POLARITY_FALLING;
    ic_init_struct.icselection = TIMER_IC_SELECTION_INDIRECTTI;
    timer_input_capture_config(SIGNAL_PWM_Get_HTIM, TIMER_CH_1, &ic_init_struct);

    /* interrupt init*/
    NVIC_EnableIRQ(SIGNAL_PWM_Get_IRQn);

    //开始TIM工作
    /* 停用定时器 */
    timer_disable(SIGNAL_PWM_Get_HTIM);
    /* 配置通道中断 */
    timer_interrupt_enable(SIGNAL_PWM_Get_HTIM, TIMER_INT_UP);    // 使能更新中断
    timer_interrupt_enable(SIGNAL_PWM_Get_HTIM, TIMER_INT_CH1);   // 使能通道1中断
    timer_interrupt_enable(SIGNAL_PWM_Get_HTIM, TIMER_INT_CH2);   // 使能通道2中断
}

/**
  * @brief  TIM_SIGNAL_PWM清理
  * @param  NULL
  * @retval NULL
**/
void REIN_TIM_SIGNAL_PWM_DeInit(void)
{
    /* 禁用定时器中断 */
    timer_interrupt_disable(SIGNAL_PWM_Get_HTIM, TIMER_INT_UP);      // 关闭更新中断
    timer_interrupt_disable(SIGNAL_PWM_Get_HTIM, TIMER_INT_CH1);     // 关闭通道1中断
    timer_interrupt_disable(SIGNAL_PWM_Get_HTIM, TIMER_INT_CH2);     // 关闭通道2中断

    /* 停止定时器 */
    timer_disable(SIGNAL_PWM_Get_HTIM);

    /* 复位GPIO配置 */
    gpio_init(SIGNAL_PWM_PUL_GPIO_Port, GPIO_MODE_AIN, 
             GPIO_OSPEED_50MHZ, SIGNAL_PWM_PUL_Pin);  // 将引脚设置为模拟输入
}
